package com.logicalthinking.socialmall.biz;

import com.github.chenlijia1111.commonModule.utils.SpringUtil;
import com.github.chenlijia1111.utils.common.Result;
import com.github.chenlijia1111.utils.common.constant.BooleanConstant;
import com.github.chenlijia1111.utils.database.mybatis.pojo.PageInfo;
import com.github.chenlijia1111.utils.encrypt.MD5EncryptUtil;
import com.github.chenlijia1111.utils.list.Lists;
import com.github.chenlijia1111.utils.oauth.jwt.JWTUtil;
import com.logicalthinking.socialmall.common.pojo.Constants;
import com.logicalthinking.socialmall.common.vo.requestVo.admin.AdminAddParams;
import com.logicalthinking.socialmall.common.vo.requestVo.admin.AdminListQueryParams;
import com.logicalthinking.socialmall.common.vo.requestVo.admin.AdminUpdateParams;
import com.logicalthinking.socialmall.common.vo.responseVo.admin.AdminVo;
import com.logicalthinking.socialmall.common.vo.responseVo.role.RoleVo;
import com.logicalthinking.socialmall.common.vo.requestVo.admin.LoginParams;
import com.logicalthinking.socialmall.common.vo.requestVo.admin.ResetPasswordParams;
import com.logicalthinking.socialmall.entity.Admin;
import com.logicalthinking.socialmall.entity.Role;
import com.logicalthinking.socialmall.service.AdminServiceI;
import com.logicalthinking.socialmall.service.RoleServiceI;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;

import javax.servlet.http.HttpServletResponse;
import java.util.*;

/**
 * 管理员用户
 *
 * @author chenLiJia
 * @since 2020-02-17 14:43:59
 **/
@Service
public class AdminBiz {

    @Autowired
    private AdminServiceI adminService;//后台管理用户
    @Autowired
    private RoleServiceI roleService;//角色

    /**
     * 添加用户
     *
     * @param params
     * @return
     */
    public Result add(AdminAddParams params) {

        //数据转化
        Admin admin = new Admin();
        BeanUtils.copyProperties(params, admin);

        admin.setCreateTime(new Date()).setUpdateTime(new Date()).
                setDeleteStatus(BooleanConstant.NO_INTEGER).setOpenStatus(BooleanConstant.YES_INTEGER);

        //密码加盐
        String password = MD5EncryptUtil.MD5StringToHexString(params.getPassword() + Constants.PASSWORD_SALT);
        admin.setPassword(password);

        return adminService.add(admin);
    }

    /**
     * 删除用户
     *
     * @param id
     * @return
     */
    public Result delete(Integer id) {

        Admin adminCondition = new Admin().setId(id).setDeleteStatus(BooleanConstant.NO_INTEGER);
        List<Admin> admins = adminService.listByCondition(adminCondition);
        if (Lists.isEmpty(admins)) {
            return Result.failure("数据不存在");
        }

        Admin admin = admins.get(0);
        admin.setDeleteStatus(BooleanConstant.YES_INTEGER);
        return adminService.update(admin);
    }

    /**
     * 批量删除用户
     *
     * @param idList
     * @return
     */
    @Transactional
    public Result batchDelete(List<Integer> idList) {
        if (Lists.isEmpty(idList)) {
            return Result.failure("未选中要删除的用户");
        }

        for (Integer id : idList) {
            Result result = delete(id);
            if (!result.getSuccess()) {
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return result;
            }
        }
        return Result.success("操作成功");
    }

    /**
     * 修改用户信息
     *
     * @param params
     * @return
     */
    public Result update(AdminUpdateParams params) {

        //数据转换
        Admin admin = new Admin();
        BeanUtils.copyProperties(params, admin);
        admin.setUpdateTime(new Date());

        return adminService.update(admin);
    }

    /**
     * 主键查询用户信息
     *
     * @param id
     * @return
     */
    public Result findById(Integer id) {

        //查询
        Admin adminCondition = new Admin().setId(id).setDeleteStatus(BooleanConstant.NO_INTEGER);
        List<Admin> admins = adminService.listByCondition(adminCondition);
        if (Lists.isEmpty(admins)) {
            return Result.failure("数据不存在");
        }

        Admin admin = admins.get(0);

        //转化
        AdminVo adminVo = new AdminVo();
        BeanUtils.copyProperties(admin, adminVo);

        //查询角色
        if (Objects.nonNull(adminVo.getRoleId())) {
            Role roleCondition = new Role().setId(adminVo.getRoleId()).setDeleteStatus(BooleanConstant.NO_INTEGER);
            List<Role> roles = roleService.listByCondition(roleCondition);
            if (Lists.isNotEmpty(roles)) {
                Role role = roles.get(0);
                adminVo.setRoleName(role.getRoleName());
            }
        }
        return Result.success("查询成功", adminVo);
    }

    /**
     * 列表查询用户信息
     *
     * @param params
     * @return
     */
    public Result listPage(AdminListQueryParams params) {
        List<AdminVo> adminVos = adminService.listPage(params);
        PageInfo<AdminVo> pageInfo = new PageInfo<>(adminVos);
        return Result.success("查询成功", pageInfo);
    }

    /**
     * 重置密码
     *
     * @param id
     * @return
     */
    public Result resetPassword(Integer id) {

        //查询用户
        Admin adminCondition = new Admin().setId(id).setDeleteStatus(BooleanConstant.NO_INTEGER);
        List<Admin> admins = adminService.listByCondition(adminCondition);
        if (Lists.isEmpty(admins)) {
            return Result.failure("数据不存在");
        }

        Admin admin = admins.get(0);

        String password = MD5EncryptUtil.MD5StringToHexString(Constants.ADMIN_INIT_PASSWORD + Constants.PASSWORD_SALT);
        admin.setPassword(password);

        return adminService.update(admin);
    }

    /**
     * 修改密码
     *
     * @param params
     * @return
     */
    public Result updatePassword(ResetPasswordParams params) {

        //查询当前用户
        Optional<Admin> optional = adminService.currentAdmin();
        if (!optional.isPresent()) {
            return Result.notLogin();
        }
        Admin admin = optional.get();


        //判断旧密码是否正确
        String oldPassword = MD5EncryptUtil.MD5StringToHexString(params.getOldPassword() + Constants.PASSWORD_SALT);
        if (!Objects.equals(oldPassword, admin.getPassword())) {
            return Result.failure("密码错误");
        }

        //重置密码
        //新密码
        String newPassword = MD5EncryptUtil.MD5StringToHexString(params.getNewPassword() + Constants.PASSWORD_SALT);
        admin.setPassword(newPassword);

        return adminService.update(admin);
    }

    /**
     * 启用
     *
     * @param id
     * @return
     */
    public Result enable(Integer id) {

        //查询用户
        Admin adminCondition = new Admin().setId(id).setDeleteStatus(BooleanConstant.NO_INTEGER);
        List<Admin> admins = adminService.listByCondition(adminCondition);
        if (Lists.isEmpty(admins)) {
            return Result.failure("数据不存在");
        }

        Admin admin = admins.get(0);

        admin.setOpenStatus(BooleanConstant.YES_INTEGER);

        return adminService.update(admin);
    }

    /**
     * 批量启用
     *
     * @param idList
     * @return
     */
    @Transactional
    public Result batchEnable(List<Integer> idList) {

        if (Lists.isEmpty(idList)) {
            return Result.failure("未选中用户");
        }

        for (Integer id : idList) {
            Result result = enable(id);
            if (!result.getSuccess()) {
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return result;
            }
        }
        return Result.success("操作成功");
    }

    /**
     * 禁用
     *
     * @param id
     * @return
     */
    public Result disable(Integer id) {
        //查询用户
        Admin adminCondition = new Admin().setId(id).setDeleteStatus(BooleanConstant.NO_INTEGER);
        List<Admin> admins = adminService.listByCondition(adminCondition);
        if (Lists.isEmpty(admins)) {
            return Result.failure("数据不存在");
        }

        Admin admin = admins.get(0);

        admin.setOpenStatus(BooleanConstant.NO_INTEGER);

        return adminService.update(admin);
    }

    /**
     * 批量禁用
     *
     * @param idList
     * @return
     */
    @Transactional
    public Result batchDisable(List<Integer> idList) {
        if (Lists.isEmpty(idList)) {
            return Result.failure("未选中用户");
        }

        for (Integer id : idList) {
            Result result = disable(id);
            if (!result.getSuccess()) {
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return result;
            }
        }
        return Result.success("操作成功");
    }

    /**
     * 登陆
     *
     * @param params
     * @return
     */
    public Result login(LoginParams params) {

        //查询用户
        Admin adminCondition = new Admin().setAccount(params.getAccount()).setDeleteStatus(BooleanConstant.NO_INTEGER);
        List<Admin> admins = adminService.listByCondition(adminCondition);
        if (Lists.isEmpty(admins)) {
            return Result.failure("用户不存在");
        }

        Admin admin = admins.get(0);
        //判断密码是否正确
        String password = MD5EncryptUtil.MD5StringToHexString(params.getPassword() + Constants.PASSWORD_SALT);
        if (!Objects.equals(password, admin.getPassword())) {
            return Result.failure("密码错误");
        }

        //登陆成功
        HashMap<String, Object> resultMap = new HashMap<>();
        resultMap.put("adminInfo", admin);
        //返回token
        String jwtToken = JWTUtil.createJWT(String.valueOf(admin.getId()), admin.getName(), Constants.ADMIN_LOGIN_LIMIT_TIME_SECONDS * 1000L, Constants.JWT_SIGN_KEY);
        //RequestContextHolder
        HttpServletResponse response = SpringUtil.getCurrentResponse();
        //将token放在response的header中
        response.setHeader(Constants.TOKEN, jwtToken);

        //查询用户权限
        Integer roleId = admin.getRoleId();
        if (Objects.nonNull(roleId)) {
            List<Role> roles = roleService.listByCondition(new Role().setId(roleId).setDeleteStatus(BooleanConstant.NO_INTEGER));
            if (Lists.isNotEmpty(roles)) {
                Role role = roles.get(0);
                RoleVo roleVo = new RoleVo();
                BeanUtils.copyProperties(role, roleVo);
                roleService.getFullInfoWithRoleVo(Lists.asList(roleVo));

                resultMap.put("authList", roleVo.getAuthList());
            }
        }

        return Result.success("登陆成功", resultMap);
    }

}
